/* 
 * AndFollowerStat
 * 
 * Copyright (C) 2009  Daniel Czerwonk <d.czerwonk@googlemail.com>
 * 
 * This program is free software: you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation, either version 3 of the License, or
 * (at your option) any later version.
 * 
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 * 
 * You should have received a copy of the GNU General Public License
 * along with this program.  If not, see <http://www.gnu.org/licenses/>.
 */
package de.dan_nrw.android.followerstat.client.followers;

import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;

import android.graphics.Bitmap;
import android.os.Handler;
import android.os.Looper;
import android.os.Message;
import android.widget.ImageView;

import de.dan_nrw.android.followerstat.Follower;
import de.dan_nrw.android.followerstat.dao.folllowers.ITwitterFollowerDAO;
import de.dan_nrw.android.followerstat.dao.folllowers.TwitterRequestException;


/**
 * @author Daniel Czerwonk
 *
 */
public class FollowerImageUpdateTaskManager extends Handler {

	private final ITwitterFollowerDAO followerDAO;
	private final Map<String, Bitmap> imageCache;
	private final Map<Integer, ImageView> viewAssignments;
	private final UpdateImagesThread thread; 
	private int id;

	
	/**
	 * Creates a new instance of FollowerImageUpdateTaskManager.
	 * @param followerDAO
	 */
	public FollowerImageUpdateTaskManager(ITwitterFollowerDAO followerDAO) {
	    super();
	    
	    this.followerDAO = followerDAO;
	    this.imageCache = new ConcurrentHashMap<String, Bitmap>();
	    
	    this.viewAssignments = new ConcurrentHashMap<Integer, ImageView>();
	    
	    this.thread = new UpdateImagesThread();
	    
	    new Thread(this.thread).start();
    }

    
	public void updateFollowerImage(ImageView imageView, Follower follower) {
		this.viewAssignments.put(++this.id, imageView);
		
		Message message = new Message();
		
		message.obj = follower;
		message.what = this.id;
		
		this.thread.updateImagesHandler.sendMessage(message);
	}

	/* (non-Javadoc)
     * @see android.os.Handler#handleMessage(android.os.Message)
     */
    @Override
    public void handleMessage(Message msg) {
	    if (msg.obj == null
	    		|| !(msg.obj instanceof Bitmap)
	    		|| !this.viewAssignments.containsKey(msg.what)) {
	    	return;
	    }
	    
	    ImageView imageView = this.viewAssignments.get(msg.what);
    	
    	imageView.setImageBitmap((Bitmap)msg.obj);
    	
    	this.viewAssignments.remove(msg.what);
    }
    
    private void sendCallbackMessage(int id, Bitmap bitmap) {
    	Message message = new Message();
    	
    	message.obj = bitmap;
    	message.what = id;
    	
    	this.sendMessage(message);
    }
    
    public void dispose() {
    	this.thread.updateImagesHandler.sendEmptyMessage(0);
    }
    
    
    private class UpdateImagesThread implements Runnable {

    	private Handler updateImagesHandler;

    	
		/* (non-Javadoc)
         * @see java.lang.Thread#run()
         */
        @Override
        public void run() {
        	Looper.prepare();
        	
        	this.updateImagesHandler = new Handler() {

				/* (non-Javadoc)
                 * @see android.os.Handler#handleMessage(android.os.Message)
                 */
                @Override
                public void handleMessage(Message msg) {
                	if (msg.what == 0) {
                		Looper.myLooper().quit();
                		
                		return;
                	}
                	
            	    if (msg.obj == null
            	    		|| !(msg.obj instanceof Follower)) {
            	    	return;
            	    }
                	
                	sendCallbackMessage(msg.what, getBitmap((Follower)msg.obj));
                }
        	};
        	
        	Looper.loop();
        }
        
        private Bitmap getBitmap(Follower follower) {
        	if (imageCache.containsKey(follower.getDisplayName())) {
        		return imageCache.get(follower.getDisplayName());
        	}
        	
            try {
            	Bitmap bitmap = followerDAO.getFollowerImage(follower);
	            
	            if (bitmap != null) {
	        		imageCache.put(follower.getDisplayName(), bitmap);
	        	}
	        	
	            return bitmap;
            }
            catch (TwitterRequestException ex) {
	            return null;
            } 
        }
    }
}